package vn.edu.ptithcm.pim.dao;

import java.util.List;

import org.hibernate.Criteria;
import org.hibernate.LockMode;
import org.hibernate.Transaction;
import org.hibernate.criterion.Order;
import org.hibernate.criterion.Projections;
import org.hibernate.criterion.Restrictions;
import org.springframework.orm.hibernate3.support.HibernateDaoSupport;

import vn.edu.ptithcm.pim.dom.Resource;

@SuppressWarnings("rawtypes")
public class ResourceDao extends HibernateDaoSupport {

	public void save(Resource resources) {
		try {
			Transaction tx = getSession().beginTransaction();
			getHibernateTemplate().save(resources);
			tx.commit();
		} catch (RuntimeException re) {
			throw re;
		}
	}

	public void saveOrUpdate(Resource resources) {
		try {
			Transaction tx = getSession().beginTransaction();
			getHibernateTemplate().saveOrUpdate(resources);
			tx.commit();
		} catch (RuntimeException re) {
			throw re;
		}
	}

	public void lock(Resource resources) {
		try {
			Transaction tx = getSession().beginTransaction();
			getHibernateTemplate().lock(resources, LockMode.NONE);
			tx.commit();
		} catch (RuntimeException re) {
			throw re;
		}
	}

	public void delete(Resource resources) {
		try {
			Transaction tx = getSession().beginTransaction();
			getHibernateTemplate().delete(resources);
			tx.commit();
		} catch (RuntimeException re) {
			throw re;
		}
	}

	public Resource merge(Resource resources) {
		try {
			return (Resource) getHibernateTemplate().merge(resources);
		} catch (RuntimeException re) {
			throw re;
		}
	}

	public Resource findById(java.lang.Long id) {
		try {
			return (Resource) getHibernateTemplate().get(Resource.class, id);
		} catch (RuntimeException re) {
			throw re;
		}
	}

	public List findByExample(Resource Resources) {
		try {
			return getHibernateTemplate().findByExample("Resources", Resources);
		} catch (RuntimeException re) {
			throw re;
		}
	}

	@SuppressWarnings("unchecked")
	public List<Resource> findByTask(Long taskid) {
		try {
			Criteria c = getSession().createCriteria(Resource.class);
			c.add(Restrictions.eq("subjectId", taskid));
			c.add(Restrictions.eq("subjectType", "Task"));
			return c.list();
		} catch (RuntimeException re) {
			throw re;
		}
	}

	@SuppressWarnings("unchecked")
	public List<Resource> findByProject(Long projectid, Long categoryId) {
		try {
			Criteria c = getSession().createCriteria(Resource.class);
			c.add(Restrictions.eq("subjectId", projectid));
			c.add(Restrictions.eq("subjectType", "Project"));
			c.add(Restrictions.eq("categoryId", categoryId));
			c.addOrder(Order.desc("lastUpdated"));
			return c.list();
		} catch (RuntimeException re) {
			throw re;
		}
	}

	@SuppressWarnings("unchecked")
	public List<Resource> findByProject(Long projectid) {
		try {
			Criteria c = getSession().createCriteria(Resource.class);
			c.add(Restrictions.eq("subjectId", projectid));
			c.add(Restrictions.eq("subjectType", "Project"));
			return c.list();
		} catch (RuntimeException re) {
			throw re;
		}
	}

	@SuppressWarnings("unchecked")
	public List<Long> getAvailableResourceCategoryIds(Long projectid) {
		try {
			Criteria c = getSession().createCriteria(Resource.class);
			c.add(Restrictions.eq("subjectType", "Project"));
			c.add(Restrictions.eq("subjectId", projectid));
			c.setProjection(Projections.distinct(Projections
					.property("categoryId")));
			return c.list();
		} catch (RuntimeException re) {
			throw re;
		}
	}

	public List getAll() {
		try {
			return getHibernateTemplate().loadAll(Resource.class);
		} catch (RuntimeException re) {
			throw re;
		}
	}

	@SuppressWarnings("unchecked")
	public List<Resource> getResourcesForSlideShow(int slideShowCount) {
		try {
			Criteria c = getSession().createCriteria(Resource.class);
			c.add(Restrictions.eq("subjectType", "SlideShow"));
			c.setMaxResults(slideShowCount);
			c.addOrder(Order.desc("lastUpdated"));
			return c.list();
		} catch (RuntimeException re) {
			throw re;
		}
	}

	public void deleteByProjectId(java.lang.Long id) {
		try {
			Transaction tx = getSession().beginTransaction();
			StringBuilder sql = new StringBuilder();
			sql.append(
					"delete Resource as resource where resource.subjectType like '%Project%' and resource.subjectId ='")
					.append(id).append("'");
			getHibernateTemplate().bulkUpdate(sql.toString());
			tx.commit();
		} catch (RuntimeException re) {
			throw re;
		}
	}

	public void deleteByTaskId(java.lang.Long id) {
		try {
			Transaction tx = getSession().beginTransaction();
			StringBuilder sql = new StringBuilder();
			sql.append(
					"delete Resource as resource where resource.subjectType like '%Task%' and resource.subjectId ='")
					.append(id).append("'");
			getHibernateTemplate().bulkUpdate(sql.toString());
			tx.commit();
		} catch (RuntimeException re) {
			throw re;
		}
	}
}
